package com.rtf.framework.web.mvc.rest.curd;

import com.google.common.collect.Lists;
import com.rtf.framework.common.dto.UtilDTO;
import com.rtf.framework.common.dto.params.AppBaseIdParam;
import com.rtf.framework.common.support.dao.entity.AppJpaIdEntity;
import com.rtf.framework.common.support.service.AppBaseDataService;
import com.rtf.framework.common.util.UtilCollection;
import com.rtf.framework.web.http.ResponseParam;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;

import java.util.List;
import java.util.Set;
import java.util.stream.Collectors;

/**
 * 应用接口功能适配器，将常用的前端restful接口的处理过程流程化和可配置化
 *
 * @param <T>
 * @param <ID>
 * @param <S>
 */
public abstract class AppFunAdaptorController<T extends AppJpaIdEntity, ID extends Long, S extends AppBaseDataService<T, ID>> extends AppFunQueryController<T,ID,S> {


    /**
     * 获取需要更新的字段
     *
     * @param targetEntity
     * @return
     */
    public Set<String> getUpdateFields(T targetEntity) {
        return UtilDTO.toDTOExcludeFields(targetEntity, Lists.newArrayList("id")).keySet();
    }

    /**
     * 保存之后处理
     *
     * @param targetEntity
     * @param type
     */
    public void postSaveHandle(T targetEntity, String type) {

    }

    /**
     * 保存实体对象 。在保存之前进行后端实体属性的验证，保证添加的数据符合业务要求。<br>
     * 如果实体id不为空，进行更新操作，否则进行添加。
     *
     * @param targetEntity
     * @return
     * @throws Exception
     */
    @PostMapping("/save")
    public ResponseParam save(@RequestBody T targetEntity) {
        //id不为空，进行更新操作，否则进行添加
        if (targetEntity.getId() != null) {
            //由请求参数中获取需要更新的字段
            Set<String> updateFields = getUpdateFields(targetEntity);
            getTargetService().update(targetEntity, updateFields);
            postSaveHandle(targetEntity, "update");
            return ResponseParam.updateSuccess();
        } else {
            getTargetService().save(targetEntity);
            postSaveHandle(targetEntity, "save");
            return ResponseParam.saveSuccess().data(targetEntity);
        }
    }

    /**
     * 删除信息
     *
     * @param ids
     * @return
     */
    @PostMapping("/delete")
    public ResponseParam delete(@RequestBody List<AppBaseIdParam> ids) {
        if (UtilCollection.isEmpty(ids)) {
            return ResponseParam.deleteFail();
        }

        List<ID> targetIds = (List<ID>) ids.stream().map(map -> map.getId()).collect(Collectors.toList());

        getTargetService().delete(targetIds);

        return ResponseParam.deleteSuccess();
    }

}
